<?php

namespace App\Library\Util;

class SignUtil
{
    use Singleton;

    public function buildLzActivitySign($data)
    {
        $sort = $this->jsonSort($data);
        $utf8 = $this->toUtf8($sort);
        return $this->shaDigest($utf8);

    }

    private function shaDigest($input)
    {
        // 使用 PHP 的 hash 函数来计算 SHA-256 摘要
        // 'sha256' 是 SHA-256 算法的名字
        // 'raw' 表示返回原始二进制数据而不是十六进制格式
        $digest = hash('sha256', $input, true);

        // 将二进制数据转换为十六进制表示形式
        // bin2hex 用于将二进制字符串转换为十六进制字符串
        $hexDigest = bin2hex($digest);

        return $hexDigest;
    }

    private function jsonSort($data)
    {
        // 获取对象的所有键
        $keys = array_keys($data);
        // 对键进行排序
        sort($keys);

        // 初始化结果字符串
        $result = "";

        // 遍历排序后的键
        foreach ($keys as $key) {
            // 判断特殊键 "G-COMT-Authorization"
            if ($key === "G-COMT-Authorization") {
                $result .= isset($data[$key]) ? $key . $data[$key] : "";
            } elseif (isset($data[$key])) {
                // 如果值存在，拼接键和值
                $result .= $key . $data[$key];
            } elseif ($data[$key] === "0") {
                // 如果值为 "0"，也拼接键和值
                $result .= $key . "0";
            }
        }

        // 返回结果字符串
        return $result;
    }

    private function toUtf8($str)
    {
        // 检查 mbstring 扩展是否可用
        if (function_exists('mb_convert_encoding')) {
            // 使用 mb_convert_encoding 进行编码转换
            return mb_convert_encoding($str, 'UTF-8');
        } else {
            // 使用 urlencode 和字符串替换模拟 encodeURI 的行为
            $encodedStr = urlencode($str);
            $utf8Str = '';
            $length = strlen($encodedStr);
            for ($i = 0; $i < $length; $i++) {
                if ($encodedStr[$i] === '%') {
                    // 处理转义序列
                    $utf8Str .= chr(hexdec(substr($encodedStr, $i + 1, 2)));
                    $i += 2; // 跳过接下来的两个字符
                } else {
                    // 直接添加字符
                    $utf8Str .= $encodedStr[$i];
                }
            }
            return $utf8Str;
        }
    }
}
